/**
 * All Rights Reserved , Copyright (C) 2020 , 青岛鼎信通讯股份有限公司
 * BaseRemindTaskService
 * 提醒任务
 * 修改纪录
 * 2020-10-26 版本：1.0 maxiaodong 创建。
 *
 * @version 版本：1.0
 * @author 作者：maxiaodong
 * 创建日期：2020-10-26
 */
package com.topscomm.base.service.impl;

import cn.hutool.json.JSONUtil;
import com.topscomm.base.BaseRemindTemplate;
import com.topscomm.base.BaseSystemConst;
import com.topscomm.base.BaseSystemConst.NoticeTypeEnum;
import com.topscomm.base.BaseSystemConst.RemindTypeEnum;
import com.topscomm.base.BaseSystemConst.RemindUnitTypeEnum;
import com.topscomm.base.BaseSystemConst.ShareTypeEnum;
import com.topscomm.base.pojo.BasePermissionManageEntity;
import com.topscomm.base.pojo.BaseRemindConfigEntity;
import com.topscomm.base.pojo.BaseRemindTaskEntity;
import com.topscomm.base.service.IBasePermissionManageService;
import com.topscomm.base.service.IBaseRemindConfigService;
import com.topscomm.base.service.IBaseRemindTaskService;
import com.topscomm.base.service.impl.auto.BaseRemindTaskServiceAuto;
import com.topscomm.basic.BasicEntity;
import com.topscomm.basic.util.SQLAdapter;
import com.topscomm.cbo.pojo.*;
import com.topscomm.cbo.service.*;
import com.topscomm.meet.dto.ConfirmInfo;
import com.topscomm.meet.pojo.MeetManageEntity;
import com.topscomm.meet.pojo.MeetRoomApplyEntity;
import com.topscomm.meet.service.IMeetJoinConfirmService;
import com.topscomm.meet.service.IMeetManageService;
import com.topscomm.pub.util.ConvertUtil;
import com.topscomm.pub.util.DateUtil;
import com.topscomm.pub.util.StringBufferProxy;
import com.topscomm.pub.util.StringUtil;
import com.topscomm.tap.common.ParameterCache;
import com.topscomm.work.WorkSystemConst.WorkSourceTypeEnum;
import com.topscomm.work.pojo.WorkScheduleEntity;
import com.topscomm.work.pojo.WorkTaskEntity;
import com.topscomm.work.service.IWorkScheduleService;
import com.topscomm.work.service.IWorkTaskService;
import com.topscomm.work.service.impl.WorkScheduleService;
import lombok.extern.slf4j.Slf4j;
import org.joda.time.DateTime;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.context.annotation.Scope;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import java.util.*;

@Slf4j
@Service(value = "baseRemindTaskService")
@Scope(value = "singleton")
public class BaseRemindTaskService extends BaseRemindTaskServiceAuto implements IBaseRemindTaskService {
	@Autowired
	private IBaseRemindTaskService baseRemindTaskService;
	@Autowired
	private IBaseRemindConfigService baseRemindConfigService;
	@Autowired
	private IWorkScheduleService workScheduleService;
	@Autowired
	private IWorkTaskService workTaskService;
	@Autowired
	private ICboMessageAppService cboMessageAppService;
	@Autowired
	private ICboMessageMailService cboMessageMailService;
	@Autowired
	private ICboSysParamService cboSysParamService;
	@Autowired
	private IBasePermissionManageService basePermissionManageService;
	@Autowired
	private ICboUserService cboUserService;
	@Autowired
	private IMeetJoinConfirmService meetJoinConfirmService;
	@Autowired
	private IMeetManageService meetManageService;
	@Autowired
	private ICboDeptService cbodeptservice;
	@Autowired
	private ICboMessageSysService cboMessageSysService;

	/**
	 * @description:将BaseRemindConfig表等待生成消息的数据转换到BaseRemindTask表
	 * @author: maxiaodong
	 * @date: 2020年11月4日上午9:50:49
	 * @modify:
	 */
	@Override
	public void configNewToTask() {
		// 将未来7天内的数据进行处理
		Calendar calendar = Calendar.getInstance();
		calendar.setTime(new Date());
		calendar.add(Calendar.DAY_OF_MONTH, 7);
		Date topRemindTime = calendar.getTime();
		String topRemindTimeLong = SQLAdapter.toDateLong(DateUtil.dateToString(topRemindTime, "yyyy-MM-dd HH:mm:ss"));
		// 查询等待发送的提醒配置
		List<BaseRemindConfigEntity> baseRemindConfigEntityList = this.baseRemindConfigService
				.queryByWhere("(state = 0 or state is null) and (remindtime is null or remindtime<" + topRemindTimeLong + ")");
		this.insertTaskFromConfigList(baseRemindConfigEntityList);
	}

	/**
	 * @description: 检查modified日期,获取所有modified的数据，删除原来的记录，插入新的记录，
	 * @author: maxiaodong
	 * @date: 2020年11月4日上午11:22:22
	 * @modify:
	 */
	@Override
	@Transactional(rollbackFor = Exception.class)
	public void configToTaskWhereModified() {
		// 获取上次检查时间，将modified时间与上次检查的时间进行对比。
		CboSysParamEntity cboSysParamEntity = this.cboSysParamService
				.queryObjectByWhere("code='RemindCheckConfigModifiedLastRunTime'");
		String RemindCheckConfigModifiedLastRunTime = cboSysParamEntity.getParamvalue();
		List<BaseRemindConfigEntity> baseRemindConfigEntitiyList = null;
		Date timeNow = new Date();
		String timeNowStringLong = SQLAdapter.toDateLong(DateUtil.dateToString(timeNow, "yyyy-MM-dd HH:mm:ss"));
		String RemindCheckConfigModifiedLastRunTimeLong = SQLAdapter.toDateLong(RemindCheckConfigModifiedLastRunTime);
		String timeNowString = DateUtil.dateToString(timeNow, "yyyy-MM-dd HH:mm:ss");
		// 获取上次检查时间到现在时间的所有modified过的记录
		if (RemindCheckConfigModifiedLastRunTime == null || RemindCheckConfigModifiedLastRunTime.equals("")) {
			StringBufferProxy queryModifiedSql = new StringBufferProxy();
			queryModifiedSql.appendSingle("(state=1 and (modifiedon != createon and modifiedon is not null) and modifiedon < {0})", timeNowStringLong);
			baseRemindConfigEntitiyList = this.baseRemindConfigService.queryByWhere(queryModifiedSql.toString());
		} else {
			StringBufferProxy queryModifiedSql = new StringBufferProxy();
			queryModifiedSql.appendSingle("( modifiedon >= {0} and modifiedon < {1} and state=1 and modifiedon != createon)", RemindCheckConfigModifiedLastRunTimeLong, timeNowStringLong);
			baseRemindConfigEntitiyList = this.baseRemindConfigService.queryByWhere(queryModifiedSql.toString());
		}
		if (baseRemindConfigEntitiyList.size() > 0) {
			// 删除所有Task表的记录
			this.deleteTaskFromConfigList(baseRemindConfigEntitiyList);
			// 重新生成Task表的记录
			this.insertTaskFromConfigList(baseRemindConfigEntitiyList);
		}
		Map<String, Object> map = new HashMap<>();
		map.put("paramvalue", timeNowString);
		// 更新RemindCheckConfigModifiedLastRunTime参数
		this.cboSysParamService.updateByWhere(map, "code='RemindCheckConfigModifiedLastRunTime'");
	}

	/**
	 * @description: 如果config记录有modified记录，删除原有task任务，要求Task记录state为0时删除
	 * @param baseRemindConfigEntities
	 * @author: maxiaodong
	 * @date: 2020年11月4日上午9:41:53
	 * @modify:
	 */
	private void deleteTaskFromConfigList(List<BaseRemindConfigEntity> baseRemindConfigEntities) {
		for (BaseRemindConfigEntity baseRemindConfigEntity : baseRemindConfigEntities) {
			String sourceid = ConvertUtil.convertToString(baseRemindConfigEntity.getId());
			String sourcetype = BaseRemindConfigEntity.tableName;
			this.baseRemindTaskService.deleteByWhere("(sourceid = '" + sourceid + "' and sourcetype = '" + sourcetype
					+ "' and (state = 0 or state is null))");
			// begintime与remindtime置空
			this.baseRemindConfigService.updateExecute("update baseRemindConfig set remindtime=null where id=" + baseRemindConfigEntity.getId());
			this.baseRemindConfigService.updateExecute("update baseRemindConfig set begintime=null where id=" + baseRemindConfigEntity.getId());
		}
	}

	/**
	 * @description: 从BaseRemindConfig表插入记录到BaseRemindTask表
	 * @param baseRemindConfigEntityList
	 * @author: maxiaodong
	 * @date: 2020年11月4日上午8:59:45
	 * @modify:
	 */
	@Transactional(rollbackFor = Exception.class)
	public void insertTaskFromConfigList(List<BaseRemindConfigEntity> baseRemindConfigEntityList) {
		this.deleteTaskFromConfigList(baseRemindConfigEntityList);
		// 遍历提醒配置列表
		for (BaseRemindConfigEntity baseRemindConfigEntity : baseRemindConfigEntityList) {
			// 数据准备
			String sourcetype = baseRemindConfigEntity.getSourcetype();
			String sourceid = baseRemindConfigEntity.getSourceid();
			// 仅仅对日程表的来源的数据进行检测
			if (!"workSchedule".equals(sourcetype) || sourceid == null || "".equals(sourceid)) {
				// 将错误数据state置为99
				this.baseRemindConfigService.updateExecute("update BASEREMINDCONFIG set state=99 where id = "
						+ ConvertUtil.convertToString(baseRemindConfigEntity.getId()));
				continue;
			}
			// 根据提醒类型获取不同提醒时间
			Date remindTime = null;
			String textContent = null;
			String place = null;
			// 根据不同的来源表获取不同的数据库连接，包括schedule与task，获取内容与开始时间。
			Map<String, Object> taskInfo = getTaskInfo(sourcetype, sourceid);
			place = ConvertUtil.convertToString(taskInfo.get("place"));
			if (taskInfo.size() == 0) {
				// 将错误数据state置为99
				this.baseRemindConfigService.updateExecute("update BASEREMINDCONFIG set state=99 where id = "
						+ ConvertUtil.convertToString(baseRemindConfigEntity.getId()));
				continue;
			}
			// 提醒类型，当天时刻还是开始时间提前配置的方式
			String remindType = baseRemindConfigEntity.getRemindtype();
			if (RemindTypeEnum.EarlierBegintime.equals(remindType)) {
				// 提前几天通知
				textContent = ConvertUtil.convertToString(taskInfo.get("textContent"));
				Date begintime = ConvertUtil.convertToDate(taskInfo.get("begintime"));
				// 计算提醒时间
				// 获取提醒的提前单位
				String taskUnit = baseRemindConfigEntity.getUnit();
				// int taskValue =
				// ConvertUtil.convertToInt(baseRemindConfigEntity.getValue());
				int taskValue;
				try {
					// 开始时间提前类型中，若value值不为数字，config表state转化为99
					taskValue = ConvertUtil.convertToInt(baseRemindConfigEntity.getValue());
				} catch (Exception e) {
					e.printStackTrace();
					this.baseRemindConfigService.updateExecute("update BASEREMINDCONFIG set state=99 where id = "
							+ ConvertUtil.convertToString(baseRemindConfigEntity.getId()));
					continue;
				}
				Calendar calendar = Calendar.getInstance();
				calendar.setTime(begintime);
				if (taskUnit.equals(RemindUnitTypeEnum.Minute)) {
					calendar.add(Calendar.MINUTE, -1 * taskValue);
				} else if (taskUnit.equals(RemindUnitTypeEnum.Hour)) {
					calendar.add(Calendar.HOUR, -1 * taskValue);
				} else if (taskUnit.equals(RemindUnitTypeEnum.Day)) {
					calendar.add(Calendar.DAY_OF_MONTH, -1 * taskValue);
				}
				remindTime = calendar.getTime();
			} else if (RemindTypeEnum.FixedBegintime.equals(remindType)) {
				textContent = ConvertUtil.convertToString(taskInfo.get("textContent"));
				String begintimeDay = DateUtil.dateToString(ConvertUtil.convertToDate(taskInfo.get("begintime")), "yyyy-MM-dd");
				remindTime = DateUtil.stringToDate(begintimeDay + " " + baseRemindConfigEntity.getValue());
			} else {
				// remindtype为非法数据
				// 将错误数据state置为99
				this.baseRemindConfigService.updateExecute("update BASEREMINDCONFIG set state=99 where id = "
						+ ConvertUtil.convertToString(baseRemindConfigEntity.getId()));
			}
			if (remindTime == null) {
				// 将错误数据state置为99
				this.baseRemindConfigService.updateExecute("update BASEREMINDCONFIG set state=99 where id = "
						+ ConvertUtil.convertToString(baseRemindConfigEntity.getId()));
				//错误数据直接continue
				continue;
			}
			// 提醒时间
			String remindTimeString = DateUtil.dateToString(remindTime, "yyyy-MM-dd HH:mm:ss");
			// 若提醒时间超前7天，不写入Task
			Calendar calendar = Calendar.getInstance();
			calendar.setTime(new Date());
			calendar.add(Calendar.DAY_OF_MONTH, 7);
			Date topRemindTime = calendar.getTime();
			long topRemindTimeLong = topRemindTime.getTime();
			long remindTimeLong = remindTime.getTime();
			String remindTimeStringDateLong = SQLAdapter.toDateLong(remindTimeString);
			// 插入config表的提醒时间,开始时间
			this.baseRemindConfigService.updateExecute("update baseRemindConfig set remindtime="
					+ remindTimeStringDateLong + " where id=" + baseRemindConfigEntity.getId());
			// 获取开始时间并插入
			String begintimeLong = SQLAdapter
					.toDateLong(DateUtil.dateToString((Date) taskInfo.get("begintime"), "yyyy-MM-dd HH:mm:ss"));
			this.baseRemindConfigService.updateExecute("update baseRemindConfig set begintime=" + begintimeLong
					+ " where id=" + baseRemindConfigEntity.getId());
			//若提醒时间大于当前时间 则不将config添加到task中 即暂不生成提醒
			if (remindTimeLong > topRemindTimeLong) {
				continue;
			}
			// 获取任务的来自部门与人员
			String taskFrom = ConvertUtil.convertToString(taskInfo.get("taskFrom"));
			// 获取所有的共享人
			StringBufferProxy querySharersSql = new StringBufferProxy();
			querySharersSql.appendSingle("sourceid = '{0}' and sourcetype = '{1}'", sourceid, sourcetype);
			List<BasePermissionManageEntity> basePermissionManageEntityList = this.basePermissionManageService
					.queryByWhere(querySharersSql.toString());
			Map<String, Object> sharesMap = new HashMap<>();
			for (BasePermissionManageEntity basePermissionManageEntity : basePermissionManageEntityList) {
				String sharetype = basePermissionManageEntity.getSharetype();
				String shareobjects = basePermissionManageEntity.getShareobjects();
				// 把所有的shareobjects全部拆成人。然后打成一个set
				if (ShareTypeEnum.Dept.equals(sharetype)) {
					sharesMap.put("deptcodes", shareobjects);
				} else if (ShareTypeEnum.Team.equals(sharetype)) {
					sharesMap.put("teamids", shareobjects);
				} else if (ShareTypeEnum.Role.equals(sharetype)) {
					sharesMap.put("roleids", shareobjects);
				} else if (ShareTypeEnum.User.equals(sharetype)) {
					sharesMap.put("usercodes", shareobjects);
				} else if (ShareTypeEnum.Share.equals(sharetype)) {
					sharesMap.put("sharecodes", shareobjects);
				}
			}
			Set<String> sharers = this.basePermissionManageService.findAllSharersByMap(sharesMap);
			List<String> sharersList = new ArrayList<>(sharers);
			List<List<String>> sharersGroupList = new ArrayList<>();
			// 将sharers按照100条记录为最大条数进行分拆
			int sharersSize = sharersList.size();
			int toIndex = 100;
			for (int i = 0; i < sharersSize; i += 100) {
				if (i + 100 > sharersSize) {
					toIndex = sharersSize - i;
				}
				List<String> newList = sharersList.subList(i, i + toIndex);
				sharersGroupList.add(newList);
			}
			// 按照分组获取CboUserEntity
			List<CboUserEntity> cboUserEntityList = new ArrayList<>();
			for (List<String> sharersGroup : sharersGroupList) {
				StringBufferProxy querySharersGroupSql = new StringBufferProxy();
				querySharersGroupSql.appendSingle("code in ('{0}')", String.join("','", sharersGroup));
				List<CboUserEntity> cboUserEntityGroupList = this.cboUserService
						.queryByWhere(querySharersGroupSql.toString());
				cboUserEntityList.addAll(cboUserEntityGroupList);
			}
			List<BasicEntity> baseRemindTaskEntityList = new ArrayList<>();
			// 形成所有待插入Task
			String beginTimeContent = WorkScheduleService.getDateStringWithWeek(ConvertUtil.convertToDate(taskInfo.get("begintime")));
			// 判断sourcetype是否是日程，若是日程则得到日程Templatetype
			String templatetype = "";
			WorkScheduleEntity workScheduleEntity = this.workScheduleService.queryById(sourceid);
			if (workScheduleEntity != null) {
				templatetype = workScheduleEntity.getTemplatetype();
			}
			for (CboUserEntity cboUserEntity : cboUserEntityList) {
				BaseRemindTaskEntity baseRemindTaskEntity = new BaseRemindTaskEntity();
				baseRemindTaskEntity.setEmail(cboUserEntity.getEmail());
				baseRemindTaskEntity.setUserid(cboUserEntity.getId());
				baseRemindTaskEntity.setUsercode(cboUserEntity.getCode());
				baseRemindTaskEntity.setUsername(cboUserEntity.getName());
				baseRemindTaskEntity.setRemindtime(remindTime);
				//设定提醒类型
				baseRemindTaskEntity.setSourceaction(BaseSystemConst.BaseActionType.Remind);
				baseRemindTaskEntity.setSourceid(ConvertUtil.convertToString(baseRemindConfigEntity.getId()));
				baseRemindTaskEntity.setSourcetype(BaseRemindConfigEntity.tableName);
				baseRemindTaskEntity.setFormid(ConvertUtil.convertToString(baseRemindConfigEntity.getSourceid()));
				baseRemindTaskEntity.setFormtype(ConvertUtil.convertToString(baseRemindConfigEntity.getSourcetype()));
				baseRemindTaskEntity.setNoticetype(baseRemindConfigEntity.getNoticetype());
				String remindContent = "";
				if (StringUtil.isEmpty(place)) {
					remindContent = String.format(BaseRemindTemplate.AppRemindTemplate.AppInnerRemindTemplate1, beginTimeContent, textContent, taskFrom);
				} else {
					if (!StringUtil.isEmpty(templatetype)) {
						// 会议室申请通知做准备工作人员的消息模板，若日程的templateType非空，则使用该模板
						remindContent = String.format(BaseRemindTemplate.AppRemindTemplate.TemplateMap.get(templatetype), beginTimeContent, place, taskFrom);
					} else {
						remindContent = String.format(BaseRemindTemplate.AppRemindTemplate.AppInnerRemindTemplate2, beginTimeContent, textContent, place, taskFrom);
					}
				}
				baseRemindTaskEntity.setContent(remindContent);
				baseRemindTaskEntity.setSubject(BaseRemindTemplate.AppRemindTemplate.AppInnerSubjectTemplate);
				baseRemindTaskEntityList.add(baseRemindTaskEntity);
			}
			// 统一插入RemindTask表
			this.baseRemindTaskService.insertBatch(baseRemindTaskEntityList);
			this.baseRemindConfigService.updateExecute("update BASEREMINDCONFIG set state=1 where id = "
					+ ConvertUtil.convertToString(baseRemindConfigEntity.getId()));
		}
	}

	/**
	 * @description: 获取任务的来自部门与人员
	 * @param handleusercode
	 * @param handleusername
	 * @return
	 * @author: maxiaodong
	 * @date: 2020年12月2日下午1:48:25
	 * @modify:
	 */
	private String getRemindSource(String handleusercode, String handleusername, String sourcetype) {
		String taskFrom = "";
		if ("".equals(sourcetype) || sourcetype == null || WorkSourceTypeEnum.WorkTask.equals(sourcetype)) {
			StringBufferProxy queryFromUserSql = new StringBufferProxy();
			queryFromUserSql.appendSingle("code in ('{0}')", handleusercode);
			// 获取来源
			List<CboUserEntity> cboUserEntityFromList = this.cboUserService.queryByWhere(queryFromUserSql.toString());
			if (cboUserEntityFromList.size() == 1) {
				// 获取部门描述
				CboDeptEntity cboDeptEntity = this.cbodeptservice
						.queryObjectByWhere("id in ('" + cboUserEntityFromList.get(0).getDeptid() + "')");
				taskFrom = cboDeptEntity.getFullname() + "\\" + handleusername;
			}
		} else if (WorkSourceTypeEnum.MeetManageType.equals(sourcetype) || MeetRoomApplyEntity.tableName.equals(sourcetype)) {
			taskFrom = handleusername;
		} else {
			// sourcetype为MCR流程相关
			StringBufferProxy queryFromUserSql = new StringBufferProxy();
			queryFromUserSql.appendSingle("code in ('{0}')", handleusercode);
			// 获取来源
			List<CboUserEntity> cboUserEntityFromList = this.cboUserService.queryByWhere(queryFromUserSql.toString());
			if (cboUserEntityFromList.size() == 1) {
				// 获取部门描述
				CboDeptEntity cboDeptEntity = this.cbodeptservice
						.queryObjectByWhere("id in ('" + cboUserEntityFromList.get(0).getDeptid() + "')");
				taskFrom = cboDeptEntity.getFullname() + "\\" + handleusername;
			}
		}
		return taskFrom;
	}

	/**
	 * @description: 获取日程的提醒时间与内容
	 * @return
	 * @author: maxiaodong
	 * @date: 2020年11月12日下午4:19:03
	 * @modify:
	 */
	private Map<String, Object> getTaskInfo(String sourcetype, String sourceid) {
		Date begintime = null;
		String textContent = null;
		Map<String, Object> returnMap = new HashMap<>();
		if (WorkSourceTypeEnum.WorkTask.equals(sourcetype)) {
			WorkTaskEntity workTaskEntity = this.workTaskService.queryById(sourceid);
			if (workTaskEntity == null) {
				return returnMap;
			}
			textContent = ConvertUtil.convertToString(workTaskEntity.getName()) + "\n"
					+ ConvertUtil.convertToString(workTaskEntity.getContent());
			begintime = workTaskEntity.getBegintime();
		} else if (WorkSourceTypeEnum.WorkSchedule.equals(sourcetype)) {
			WorkScheduleEntity workScheduleEntity = this.workScheduleService.queryById(sourceid);
			if (workScheduleEntity == null) {
				return returnMap;
			}
			if (workScheduleEntity.getPlace() != null) {
				returnMap.put("place", workScheduleEntity.getPlace());
			}
			textContent = ConvertUtil.convertToString(workScheduleEntity.getName());
			begintime = workScheduleEntity.getBegintime();
			String handleusercodeWorkSchedule = workScheduleEntity.getHandleusercode();
			String handleusernameWorkSchedule = workScheduleEntity.getHandleusername();
			String sourcetypeWorkSchedule = workScheduleEntity.getSourcetype();
			String taskFrom = getRemindSource(handleusercodeWorkSchedule, handleusernameWorkSchedule, sourcetypeWorkSchedule);
			returnMap.put("taskFrom", taskFrom);
		} else if (WorkSourceTypeEnum.MeetManageType.equals(sourcetype)) {
			MeetManageEntity meetManageEntity = this.meetManageService.queryById(sourceid);
			if (meetManageEntity == null) {
				return returnMap;
			}
			if (meetManageEntity.getPlace() != null) {
				returnMap.put("place", meetManageEntity.getPlace());
			}
			textContent = ConvertUtil.convertToString(meetManageEntity.getName());
			begintime = meetManageEntity.getBegintime();
		} else {
			return returnMap;
		}
		returnMap.put("begintime", begintime);
		returnMap.put("textContent", textContent);
		return returnMap;
	}

	/**
	 * @description: 从BaseRemindTask表定时任务发送消息
	 * @author: maxiaodong
	 * @date: 2020年11月4日上午8:59:03
	 * @modify:
	 */
	@Override
	public void taskToMessage() {
		//当前时间不可变
		final DateTime now= new DateTime();
		// 获取发送任务的时间
		CboSysParamEntity cboSysParamEntity = this.cboSysParamService
				.queryObjectByWhere("code='RemindCheckTaskLastRunTime'");
		String remindCheckTaskLastRunTime = cboSysParamEntity.getParamvalue();
		// 获取remindtime从上次检查时间到现在时间的所有Task的记录
		String timeNowString = DateUtil.dateToString(now.toDate(), "yyyy-MM-dd HH:mm:ss");
		try {
			String timeNowStringLong = SQLAdapter.toDateLong(timeNowString);
			List<BaseRemindTaskEntity> baseRemindTaskEntityList = null;
			String remindCheckTaskLastRunEarlierTimeLong = null;
			// 系统首次运行则取当前时间  非首次运行取上次检查时间
			Date remindCheckTaskLastRunTimeDate = DateUtil.stringToDate(remindCheckTaskLastRunTime);
			final DateTime remindStartTime = new DateTime(remindCheckTaskLastRunTimeDate);
			// 上次检查时间提前5分钟，解决立即发送的问题
			remindCheckTaskLastRunEarlierTimeLong = SQLAdapter
					.toDateLong(DateUtil.dateToString(remindStartTime.minusMinutes(5).toDate(), "yyyy-MM-dd HH:mm:ss"));
			// 查询时间段内的消息
			StringBufferProxy queryTaskSql = new StringBufferProxy();
			queryTaskSql.appendSingle("( (state=0 or state is null) and remindtime >={0} and remindtime < {1})", remindCheckTaskLastRunEarlierTimeLong, timeNowStringLong);
			baseRemindTaskEntityList = this.baseRemindTaskService.queryByWhere(queryTaskSql.toString());
			// 遍历记录，如果记录不在config表则删除，如果在config表则发出。state改为1
			List<BasicEntity> baseRemindTaskEntityAppRemindList = new ArrayList<>();
			List<BasicEntity> baseRemindTaskEntityMailRemindList = new ArrayList<>();
			for (BaseRemindTaskEntity baseRemindTaskEntity : baseRemindTaskEntityList) {
				String sourceid = baseRemindTaskEntity.getSourceid();
				String sourcetype = baseRemindTaskEntity.getSourcetype();
				String formid = baseRemindTaskEntity.getFormid();
				String formType = baseRemindTaskEntity.getFormtype();
				String userCode = baseRemindTaskEntity.getUsercode();
				// 基础配置表判断是否存在源，没有源不发送
				if (BaseRemindConfigEntity.tableName.equals(sourcetype)) {
					List<BaseRemindConfigEntity> baseRemindConfigValidEntityList = this.baseRemindConfigService
							.queryByWhere("id=" + sourceid);
					if (baseRemindConfigValidEntityList.isEmpty()) {
						this.baseRemindTaskService.deleteByWhere("(sourceid='" + sourceid + "' and sourcetype = '" + sourcetype + "' and state = 0)");
						continue;
					}
				}
				// 如果最终来源类型为日程，则判断当前时间是否已经大于日程开始时间，若大于则不发送
				if (WorkSourceTypeEnum.WorkSchedule.equals(formType)) {
					WorkScheduleEntity workSchedule = workScheduleService.queryById(formid);
					// 若workSchedule为空则说明日程被删除，即消息为日程撤销消息
					if (workSchedule != null) {
						if (now.toDate().after(workSchedule.getBegintime())) {
							continue;
						}
						//正常会议发送
						if(workSchedule.getSourcetype()!=null&& MeetManageEntity.tableName.contentEquals(workSchedule.getSourcetype())){
							//不参会人员 除日程修改消息均不发送
							ConfirmInfo  confirmInfo =  this.meetJoinConfirmService.loadJoinInfo(ConfirmInfo.builder().sourceId(formid).sourceType(formType).userCode(userCode).build());
							if(confirmInfo.getConfirmState()==Boolean.FALSE &&
									!BaseSystemConst.BaseActionType.Update.contentEquals(baseRemindTaskEntity.getSourceaction())){
								continue;
							}
							//对于来源为会议的进行特殊映射，方便手机端区分
							if(confirmInfo.getShowConfirm()){
								String joinText = ParameterCache.getValue("MEET_JOIN_TEXT", "\n请点击【查看日程】按钮进入详情，确认是否参会。");
								baseRemindTaskEntity.setContent(baseRemindTaskEntity.getContent()+joinText);
							}else{
								//next featrue 强制参会
							}
						}
					}else{
						//日程撤销消息 新增类型
						baseRemindTaskEntity.setFormtype(baseRemindTaskEntity.getSourcetype()+"_"+baseRemindTaskEntity.getSourceaction());
					}
				}
				String noticetype = baseRemindTaskEntity.getNoticetype();
				if (NoticeTypeEnum.App.equals(noticetype)) {
					baseRemindTaskEntityAppRemindList.add(baseRemindTaskEntity);
				} else if ((NoticeTypeEnum.Email.equals(noticetype))) {
					baseRemindTaskEntityMailRemindList.add(baseRemindTaskEntity);
				}
			}
			if (!baseRemindTaskEntityAppRemindList.isEmpty()) {
				this.insertMessageAppFromTask(baseRemindTaskEntityAppRemindList);
			}
			if (!baseRemindTaskEntityMailRemindList.isEmpty()) {
				this.insertMessageMailFromTask(baseRemindTaskEntityMailRemindList);
			}
			Map<String, Object> map = new HashMap<>();
			map.put("paramvalue", timeNowString);
			// 更新RemindCheckConfigModifiedLastRunTime参数
			this.cboSysParamService.updateByWhere(map, "code='RemindCheckTaskLastRunTime'");
		} catch (Exception e) {
			log.error("RemindTaskToMessage异常终止，时间"+new Date(),e);
			Map<String, Object> map = new HashMap<>();
			map.put("paramvalue", timeNowString);
			// 更新RemindCheckConfigModifiedLastRunTime参数
			this.cboSysParamService.updateByWhere(map, "code='RemindCheckTaskLastRunTime'");
		}
	}

	/**
	 * @description: 发送app消息：从BaseRemindTask表插入到CboMessageApp表
	 * @param baseRemindTaskEntity
	 * @author: maxiaodong
	 * @date: 2020年11月4日上午8:55:51
	 * @modify:
	 */
	public void insertMessageAppFromTask(List<BasicEntity> baseRemindTaskEntityAppRemindList) {
		List<Map<String, Object>> cboMessageAppMapList = new ArrayList<>();
		List<String> baseRemindTaskEntityIdList = new ArrayList<>();
		List<BasicEntity> cboMessageSysEntityList = new ArrayList<>();
		for (BasicEntity baseRemindTaskEntity : baseRemindTaskEntityAppRemindList) {
			// MessageApp消息发送
			Map<String, Object> cboMessageAppMap = new HashMap<>();
			cboMessageAppMap.put(CboMessageAppEntity.FieldContent, ((BaseRemindTaskEntity) baseRemindTaskEntity).getContent());
			cboMessageAppMap.put(CboMessageAppEntity.FieldReceiverid, ((BaseRemindTaskEntity) baseRemindTaskEntity).getUserid());
			cboMessageAppMap.put("usercode", ((BaseRemindTaskEntity) baseRemindTaskEntity).getUsercode());
			cboMessageAppMap.put(CboMessageAppEntity.FieldSendtype, 0);
			cboMessageAppMap.put(CboMessageAppEntity.FieldExtendfield1, ((BaseRemindTaskEntity) baseRemindTaskEntity).getSubject());// 从task表改
			cboMessageAppMapList.add(cboMessageAppMap);
			baseRemindTaskEntityIdList.add(ConvertUtil.convertToString(baseRemindTaskEntity.getId()));
			// MessageSys消息发送
			CboMessageSysEntity cboMessageSysEntity = new CboMessageSysEntity();
			cboMessageSysEntity
					.setContent(((BaseRemindTaskEntity) baseRemindTaskEntity).getContent().replace("\n", "<br>"));
			cboMessageSysEntity.setReceivercode(((BaseRemindTaskEntity) baseRemindTaskEntity).getUsercode());
			cboMessageSysEntity.setReceivername(((BaseRemindTaskEntity) baseRemindTaskEntity).getUsername());
			cboMessageSysEntity.setSubject(((BaseRemindTaskEntity) baseRemindTaskEntity).getSubject());
			cboMessageSysEntity.setSourcetype(((BaseRemindTaskEntity) baseRemindTaskEntity).getFormtype());
			cboMessageSysEntity.setSourceid(ConvertUtil.convertToLong(((BaseRemindTaskEntity) baseRemindTaskEntity).getFormid()));
			//包装sourceaction为json格式
			Map<String,String> sourceactionMap = new HashMap<>();
			sourceactionMap.put(BaseSystemConst.BaseActionType.Code,((BaseRemindTaskEntity) baseRemindTaskEntity).getSourceaction());
			//转Obj为json字符串
			String sourceactionJson = JSONUtil.toJsonStr(sourceactionMap);
			cboMessageSysEntity.setParamvalue(sourceactionJson);
			cboMessageSysEntityList.add(cboMessageSysEntity);
		}
		// 每50条数据插一次，防止oa hessian超时
		int baseRemindTaskEntityAppRemindListSize = baseRemindTaskEntityAppRemindList.size();
		int lastIndex = 0;
		for (int i = 1; i <= baseRemindTaskEntityAppRemindListSize; i++) {
			if (i % 50 == 0 || i == (baseRemindTaskEntityAppRemindListSize)) {
				try {
					this.cboMessageAppService.insertList(cboMessageAppMapList.subList(lastIndex, i));
					this.cboMessageSysService.insertBatch(cboMessageSysEntityList.subList(lastIndex, i));
				} catch (Exception e) {
				} finally {
					this.baseRemindTaskService.updateExecute("update BASEREMINDTASK set state=1 where id in ("
							+ String.join(",", baseRemindTaskEntityIdList.subList(lastIndex, i)) + ")");
				}
				lastIndex = i;
			}
		}
	}

	/**
	 * @description:发送email消息：从BaseRemindTask表插入到CboMessageMail表
	 * @param baseRemindTaskEntity
	 * @author: maxiaodong
	 * @date: 2020年11月4日上午8:58:20
	 * @modify:
	 */
	public void insertMessageMailFromTask(List<BasicEntity> baseRemindTaskEntityMailRemindList) {
		List<BasicEntity> cboMessageMailEntityList = new ArrayList<>();
		List<String> baseRemindTaskEntityIdList = new ArrayList<>();
		for (BasicEntity baseRemindTaskEntity : baseRemindTaskEntityMailRemindList) {
			CboMessageMailEntity cboMessageMailEntity = new CboMessageMailEntity();
			cboMessageMailEntity
					.setContent(((BaseRemindTaskEntity) baseRemindTaskEntity).getContent().replace("\n", "<br>"));
			cboMessageMailEntity.setReceivermails(((BaseRemindTaskEntity) baseRemindTaskEntity).getEmail());
			cboMessageMailEntity.setSubject(((BaseRemindTaskEntity) baseRemindTaskEntity).getSubject());
			cboMessageMailEntityList.add(cboMessageMailEntity);
			baseRemindTaskEntityIdList.add(ConvertUtil.convertToString(baseRemindTaskEntity.getId()));
		}
		// 每100条数据插一次
		int baseRemindTaskEntityMailRemindListSize = baseRemindTaskEntityMailRemindList.size();
		int lastIndex = 0;
		for (int i = 1; i <= baseRemindTaskEntityMailRemindListSize; i++) {
			if (i % 100 == 0 || i == (baseRemindTaskEntityMailRemindListSize)) {
				this.cboMessageMailService.insertBatch(cboMessageMailEntityList.subList(lastIndex, i));
				this.baseRemindTaskService.updateExecute("update BASEREMINDTASK set state=1 where id in ("
						+ String.join(",", baseRemindTaskEntityIdList.subList(lastIndex, i)) + ")");
				lastIndex = i;
			}
		}
	}
}
